package org.jawa.dao.hibernate;

import java.util.List;

import javax.persistence.Table;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.jawa.dao.UserDao;
import org.jawa.model.User;
import org.springframework.core.annotation.AnnotationUtils;
import org.springframework.jdbc.core.simple.SimpleJdbcTemplate;
import org.springframework.orm.ObjectRetrievalFailureException;
import org.springframework.orm.hibernate3.SessionFactoryUtils;
import org.springframework.orm.hibernate3.support.HibernateDaoSupport;
import org.springframework.security.userdetails.UserDetails;
import org.springframework.security.userdetails.UserDetailsService;
import org.springframework.security.userdetails.UsernameNotFoundException;

/**
 * This class interacts with Spring and Hibernate to save and
 * retrieve User objects.
 *
 * @author Matt Raible
 */
public class UserDaoHibernate extends HibernateDaoSupport implements UserDao,UserDetailsService{    
    Log logger = LogFactory.getLog(UserDaoHibernate.class);
        
    @SuppressWarnings("unchecked")
	public List<User> getUsers() {
        return getHibernateTemplate().find("from User");
    }

    public User getUser(Long id) {
        User user = (User) getHibernateTemplate().get(User.class, id);
        if (user == null) {
            throw new ObjectRetrievalFailureException(User.class, id);
        }
        return user;
    }

    public User saveUser(User user) {
    	getHibernateTemplate().saveOrUpdate(user);
    	getHibernateTemplate().flush();
    	return user;
    }

    public void removeUser(Long id) {
    	getHibernateTemplate().delete(getUser(id));
    }

    /** 
     * {@inheritDoc}
    */
	public String getUserPassword(String username) {
		// TODO Auto-generated method stub
		SimpleJdbcTemplate jdbcTemplate =
            new SimpleJdbcTemplate(SessionFactoryUtils.getDataSource(getSessionFactory()));
	    Table table = AnnotationUtils.findAnnotation(User.class, Table.class);
	    return jdbcTemplate.queryForObject(
            "select password from " + table.name() + " where username=?", String.class, username);
	}

	/** 
     * {@inheritDoc}
    */
	public UserDetails loadUserByUsername(String username)
			throws UsernameNotFoundException {
		// TODO Auto-generated method stub
		List users=getHibernateTemplate().find("from User where username=?", username);
		if(users==null || users.isEmpty()){
			throw new UsernameNotFoundException("user '" + username + "' not found...");
		}else{
			return (UserDetails)users.get(0);
		}
	}
}
